package server.mobiles;

import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;

import server.main.Data;
import server.map.Gate;
import server.map.Platform;
import server.map.Stair;
import server.utility.Id;
import server.utility.Point2d;


public class PlayerMobile extends Mobile implements Serializable {
	
	private static final long serialVersionUID = 1L;
	private Id logoutMap;
	private Point2d logoutPosition;
	private int speed=10;
	private Platform platform;
	private int fallingSpeed=10;
	private boolean onStair;
	private int jumpHeight=30;
	private boolean jumping;
	

	public static PlayerMobile create(String name){
		PlayerMobile res=new PlayerMobile(new Point2d(200,400),name);
		res.logoutMap=Data.bornMap;
		res.setMap(Data.internal);
		Data.add(res);
		
		return res;
	}
	
	private PlayerMobile(Point2d pos, String name) {
		super(name);
		player=true;
		position=pos;
		logoutPosition=pos;
		health = 50;
		maxHealth = 100;
	}
	
	public void update(){
		if(jumping)
			jumping=false;
		else if(platform==null && !onStair){
			platform=Data.getMap(map).getPlatform(position);
			if(platform==null)
				this.position.plus(new Point2d(0, fallingSpeed));
			else
				this.position.setY(platform.getTopY());
		}
	}
	
	public String toString(){
		return name+";"+position+";"+id+";"+health+";"+maxHealth+";"+map+"\n";
	}
	
	public void setMap(Id m){
		super.setMap(m);
		
		platform=null;
	}

	public void moveLeft() {
		this.position.plus(new Point2d(-speed, 0));
		platform=Data.getMap(map).getPlatform(position);
		if(onStair)
			onStair=Data.getMap(map).getStair(position)!=null;
	}

	public void moveRight() {
		this.position.plus(new Point2d(speed, 0));	
		platform=Data.getMap(map).getPlatform(position);
		if(onStair)
			onStair=Data.getMap(map).getStair(position)!=null;
	}

	public void moveUp(){
		Gate gate=Data.getMap(map).getGate(position);
		if(gate!=null){
			position=gate.getDestination().copy();
			setMap(gate.getDestinationMap());
			return;
		}
		else{
			Stair s=Data.getMap(map).getStair(position);
			
			if(s!=null){
				this.position.plus(new Point2d(0, -speed));
				onStair=true;
				return;
			}
		}
		
		onStair=false;
		platform=Data.getMap(map).getPlatform(position);
	}
	
	public void moveDown(){
		Stair s=Data.getMap(map).getStair(position);
		
		if(s!=null){
			this.position.plus(new Point2d(0, speed));
			onStair=true;
			return;
		}
		
		onStair=false;
		platform=Data.getMap(map).getPlatform(position);
	}
	
	public void jump(){
		if(platform==null && !onStair)
			return;
		
		position.plus(new Point2d(0, -jumpHeight));
		platform=null;
		onStair=false;
		jumping=true;
	}

	public void login() {
		setMap(logoutMap);
		position=logoutPosition;
	}
	
	public void logout(){
		if(map.equals(Data.internal))
			return;
		logoutMap=map;
		logoutPosition=position;
		setMap(Data.internal);
	}
	
	private void readObject(ObjectInputStream in) throws IOException,
	ClassNotFoundException {
		int ver=in.readInt();
		
		switch(ver){
		
			case 1:{
				logoutMap = (Id)in.readObject();
				logoutPosition = (Point2d)in.readObject();
				speed = in.readInt();
			}
		}
	}
	
	private void writeObject(ObjectOutputStream out) throws IOException {
		out.writeInt(1); //version
		
		out.writeObject(logoutMap);
		out.writeObject(logoutPosition);
		out.writeInt(speed);
	}

}